package com.woniu.service.Impl;

import com.woniu.dao.*;
import com.woniu.service.OperateBankService;
import com.woniu.service.SearchBankService;
import com.woniu.utils.RedisUtil;
import com.woniuxy.commons.entity.*;
import com.woniuxy.commons.enums.TestBankEnum;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.EnableTransactionManagement;
import org.springframework.transaction.annotation.Transactional;

import javax.annotation.Resource;
import java.lang.reflect.Method;

/**
 * @program: bzeducation
 * @author: Xingqilin
 * @create: 2020-07-21 10:08
 * @description:题库操作
 */
@Service
@EnableTransactionManagement
public class OperateBankServiceImpl implements OperateBankService {

    @Resource
    SelectBankDao selectBankDao;
    @Resource
    VacancyBankDao vacancyBankDao;
    @Resource
    MaterialBankDao materialBankDao;
    @Resource
    ClozeBankDao clozeBankDao;
    @Resource
    JudgeBankDao judgeBankDao;
    @Resource
    ReviseBankDao reviseBankDao;
    @Resource
    WriterBankDao writerBankDao;
    @Resource
    MaterialQuestionDao materialQuestionDao;
    @Resource
    SearchBankService searchBankService;
    SearchBankServiceImpl searchBankImpl = new SearchBankServiceImpl();
    @Resource
    private RedisTemplate<String, Object> redisTemplate;

    //    选择题操作
    @Override
    public int insertSelectBank(SelectBank selectBank) {
        int i = selectBankDao.insertSelectBank(selectBank);
        return i;
    }

    @Override
    public int updateSelectBank(SelectBank selectBank) {
        deleteRedisKey(TestBankEnum.SELECT_BANK + "." + selectBank.getSelectId());
        int i = selectBankDao.updateSelectBank(selectBank);
        return i;
    }

    @Override
    public int deleteSelectBank(long selectId) {
        deleteRedisKey(TestBankEnum.SELECT_BANK + "." + selectId);
        int i = selectBankDao.deleteSelectBank(selectId);
        return i;
    }


    //    填空题操作
    @Override
    public int insertVacancyBank(VacancyBank vacancyBank) {
        int i = vacancyBankDao.insertVacancyBank(vacancyBank);
        return i;
    }

    @Override
    public int updateVacancyBank(VacancyBank vacancyBank) {
        deleteRedisKey(TestBankEnum.VACANCY_BANK + "." + vacancyBank.getVacancyId());
        int i = vacancyBankDao.updateVacancyBank(vacancyBank);
        return i;
    }

    @Override
    public int deleteVacancyBank(long vacancyId) {
        deleteRedisKey(TestBankEnum.VACANCY_BANK + "." + vacancyId);
        int i = vacancyBankDao.deleteVacancyBank(vacancyId);
        return i;
    }


    //    判断题操作
    @Override
    public int insertJudgeBank(JudgeBank judgeBank) {
        int i = judgeBankDao.insertJudgeBank(judgeBank);
        return i;
    }

    @Override
    public int updateJudgeBank(JudgeBank judgeBank) {
        deleteRedisKey(TestBankEnum.JUDGE_BANK + "." + judgeBank.getJudgeId());
        int i = judgeBankDao.updateJudgeBank(judgeBank);
        return i;
    }

    @Override
    public int deleteJudgeBank(long judgeId) {
        deleteRedisKey(TestBankEnum.JUDGE_BANK + "." + judgeId);
        int i = judgeBankDao.deleteJudgeBank(judgeId);
        return i;
    }


    //    改错题操作
    @Override
    public int insertReviseBank(ReviseBank reviseBank) {
        int i = reviseBankDao.insertReviseBank(reviseBank);
        return i;
    }

    @Override
    public int updateReviseBank(ReviseBank reviseBank) {
        deleteRedisKey(TestBankEnum.REVISE_BANK + "." + reviseBank.getReviseId());
        int i = reviseBankDao.updateReviseBank(reviseBank);
        return i;
    }

    @Override
    public int deleteReviseBank(long reviseId) {
        deleteRedisKey(TestBankEnum.REVISE_BANK + "." + reviseId);
        int i = reviseBankDao.deleteReviseBank(reviseId);
        return i;
    }


    //    作文题操作
    @Override
    public int insertWriterBank(WriterBank writerBank) {
        int i = writerBankDao.insertWriterBank(writerBank);
        return i;
    }

    @Override
    public int updateWriterBank(WriterBank writerBank) {
        deleteRedisKey(TestBankEnum.JUDGE_BANK + "." + writerBank.getWriterId());
        int i = writerBankDao.updateWriterBank(writerBank);
        return i;
    }

    @Override
    public int deleteWriterBank(long writerId) {
        deleteRedisKey(TestBankEnum.JUDGE_BANK + "." + writerId);
        int i = writerBankDao.deleteWriterBank(writerId);
        return i;
    }


    //    阅读材料题操作
    @Override
    @Transactional
    public int insertMaterialBank(MaterialBank materialBank) {
        int i = 0;
        i += materialBankDao.insertMaterialBank(materialBank);
        materialBank.getSelectBanks().forEach(item -> {
            item.setSelectSingle(false);
            selectBankDao.insertSelectBank(item);
            materialQuestionDao.insertMaterialQuestion(
                    getMaterialQustion(materialBank, item.getSelectId(), TestBankEnum.SELECT_BANK.getIndex()));
        });
        materialBank.getVacancyBanks().forEach(item -> {
            item.setVacancySingle(false);
            vacancyBankDao.insertVacancyBank(item);
            materialQuestionDao.insertMaterialQuestion(
                    getMaterialQustion(materialBank, item.getVacancyId(), TestBankEnum.VACANCY_BANK.getIndex()));
        });
        if (materialBank.getJudgeBanks() != null) {
            materialBank.getJudgeBanks().forEach(item -> {
                item.setJudgeSingle(false);
                judgeBankDao.insertJudgeBank(item);
                materialQuestionDao.insertMaterialQuestion(
                        getMaterialQustion(materialBank, item.getJudgeId(), TestBankEnum.JUDGE_BANK.getIndex()));
            });
        }
        return i;
    }

    @Override
    @Transactional
    public int updateMaterialBank(MaterialBank materialBank) {
        int i = 0;
        i += materialBankDao.updateMaterialBank(materialBank);
        materialBank.getSelectBanks().forEach(item -> {
            selectBankDao.updateSelectBank(item);
            materialQuestionDao.updateMaterialQuestion(
                    getMaterialQustion(materialBank, item.getSelectId(), TestBankEnum.SELECT_BANK.getIndex()));
        });
        materialBank.getVacancyBanks().forEach(item -> {
            vacancyBankDao.updateVacancyBank(item);
            materialQuestionDao.updateMaterialQuestion(
                    getMaterialQustion(materialBank, item.getVacancyId(), TestBankEnum.VACANCY_BANK.getIndex()));
        });
        materialBank.getJudgeBanks().forEach(item -> {
            judgeBankDao.updateJudgeBank(item);
            materialQuestionDao.updateMaterialQuestion(
                    getMaterialQustion(materialBank, item.getJudgeId(), TestBankEnum.JUDGE_BANK.getIndex()));
        });
        return i;
    }

    @Override
    @Transactional
    public int deleteMaterialBank(long materialId) {
        int i = 0;
        MaterialBank materialById = materialBankDao.findMaterialById(materialId);
        materialById.getSelectBanks().forEach(item -> {
            selectBankDao.deleteSelectBank(item.getSelectId());
        });
        materialById.getVacancyBanks().forEach(item -> {
            vacancyBankDao.deleteVacancyBank(item.getVacancyId());
        });
        materialById.getJudgeBanks().forEach(item -> {
            judgeBankDao.deleteJudgeBank(item.getJudgeId());
        });
        i += materialBankDao.deleteMaterialBank(materialId);
        i += materialQuestionDao.deleteMaterialQuestion(materialId);
        return i;
    }

    //  完型填空操作
    @Override
    @Transactional
    public int insertClozeBank(ClozeBank clozeBank) {
        int cloze = clozeBankDao.insertCloze(clozeBank);
        clozeBank.getClozeSelects().forEach(item -> item.setClozeSelectMid(clozeBank.getClozeId()));
        int selects = clozeBankDao.insertSelect(clozeBank.getClozeSelects());
        return cloze + selects;
    }

    @Override
    @Transactional
    public int updateClozeBank(ClozeBank clozeBank) {
        deleteRedisKey(TestBankEnum.CLOZE_BANK + "." + clozeBank.getClozeId());
        int i = clozeBankDao.updateCloze(clozeBank);
        i += clozeBankDao.updateClozeSelects(clozeBank.getClozeSelects());
        return i;
    }

    @Override
    @Transactional
    public int deleteClozeBank(long clozeId) {
        deleteRedisKey(TestBankEnum.CLOZE_BANK + "." + clozeId);
        int i = clozeBankDao.deleteClozeSelect(clozeId);
        i += clozeBankDao.deleteCloze(clozeId);
        return i;
    }


    //    更新删除数据后同步刷新redis数据
    private void deleteRedisKey(String keyValue) {
        String key = "";
        try {
            Method method = searchBankService.getClass().getDeclaredMethod("findBankById", TestBankEnum.class, Long.class);
            key = RedisUtil.generate("findBankById", searchBankImpl, method, keyValue);
        } catch (Exception e) {
            e.printStackTrace();
        }
        System.out.println(key);
        ValueOperations<String, Object> valueOperations = redisTemplate.opsForValue();
        redisTemplate.delete(key);
    }

    private MaterialQuestion getMaterialQustion(MaterialBank materialBank, Long Qid, Long index) {
        MaterialQuestion materialQuestion = new MaterialQuestion();
        materialQuestion.setMaterialQuesMid(materialBank.getMaterialId());
        materialQuestion.setMaterialQuesQid(Qid);
        materialQuestion.setMaterialQuesQtype(index);
        return materialQuestion;
    }
}
